/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package slicktemplate;

import java.awt.Image;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.newdawn.slick.GameContainer;
import org.newdawn.slick.Graphics;
import org.newdawn.slick.Input;
import org.newdawn.slick.SlickException;
import org.newdawn.slick.state.BasicGameState;
import org.newdawn.slick.state.StateBasedGame;

/**
 *
 * @author Josh
 */
public class LevelEditor extends BasicGameState {

    //These lists hold the lists of types of objects, which are metaphysical and kept in the class
    static ArrayList<ArrayList> renderList = new ArrayList<ArrayList>();
    static ArrayList<ArrayList> updateList = new ArrayList<ArrayList>();
    static ArrayList<ArrayList> saveToMap = new ArrayList<ArrayList>();
    static ArrayList<ArrayList> placeOverList = new ArrayList<ArrayList>();

    int stateId = 48;
    boolean drawGrid = false;
    ArrayList saving = new ArrayList();

    public LevelEditor(int stateId) {
        this.stateId = stateId;
    }

    public int getID() {
        return stateId;
    }

    @Override
    public void init(GameContainer container, StateBasedGame game) throws SlickException {
        //Adding to renderList
        renderList.clear();
        renderList.add(BuildGui.all);
        renderList.add(Wall.all);
        renderList.add(WallButton.all);
        renderList.add(Enemy1.all);
        renderList.add(WallPlacer.all);
        renderList.add(TurretPlacer.all);
        renderList.add(TurretButton.all);
        renderList.add(Turret.all);
        renderList.add(ProjectileNail.all);
        renderList.add(BasicBuilding.all);
        for (int i = 0; i < renderList.size(); i++) {
            renderList.get(i).clear();
        }
        //Adding to updateList
        updateList.clear();
        updateList.add(WallButton.all);
        updateList.add(Enemy1.all);
        updateList.add(WallPlacer.all);
        updateList.add(TurretPlacer.all);
        updateList.add(TurretButton.all);
        updateList.add(Turret.all);
        updateList.add(ProjectileNail.all);
        updateList.add(Wall.all);
        updateList.add(BasicBuilding.all);
        for (int i = 0; i < updateList.size(); i++) {
            updateList.get(i).clear();
        }

        saveToMap.add(Wall.all);
        saveToMap.add(BasicBuilding.all);
        saveToMap.add(Turret.all);
        classToArrayList.put(Wall.class, Wall.all);
        classToArrayList.put(BasicBuilding.class, BasicBuilding.all);
        classToArrayList.put(Turret.class, Turret.all);
        for (int i = 0; i < saveToMap.size(); i++) {
            saveToMap.get(i).clear();
        }
        placeOverList.add(Wall.all);
        placeOverList.add(Turret.all);
        placeOverList.add(BuildGui.all);
        placeOverList.add(BasicBuilding.all);
        new BuildGui();
        new WallButton(Game.width - Game.width / 5, 50);
        new TurretButton(Game.width - Game.width / 5, 100);
        new BasicBuilding(Game.width - Game.width / 5, 200);
    }

    @Override
    public void render(GameContainer container, StateBasedGame game, Graphics g) throws SlickException {
        if (drawGrid == true) {
            for (int i = 0; i < Game.width; i += 32) {
                g.drawLine(i, 0, i, Game.height);
            }
            for (int i = 0; i < Game.height; i += 32) {
                g.drawLine(0, i, Game.width, i);
            }
        }
        for (ArrayList<Renderable> it : renderList) { //go through all the objects and draw them
            for (Renderable obj : it) {
                obj.render(g);
            }
        }
    }

    @Override
    public void update(GameContainer container, StateBasedGame game, int delta) throws SlickException {
        Input input = container.getInput();
        if (input.isKeyPressed(input.KEY_V)) {
            if (drawGrid == false) {
                drawGrid = true;
            } else {
                drawGrid = false;
            }
        }
        if (input.isKeyPressed(Input.KEY_ESCAPE)) {//A much needed way to exit the game
            container.exit();
        }
        if (input.isKeyPressed(Input.KEY_F6)) {
            saveArray("map.td");
        }
        if (input.isKeyPressed(Input.KEY_F7)) {
            loadArray("map.td");
            for (int i = 0; i < saveToMap.size(); i++) {
                if (saveToMap.get(i).isEmpty() == false) {
                    if (saveToMap.get(i).get(0) != null) {
                        Object obj = saveToMap.get(i).get(0);
                        ArrayList ar = saveToMap.get(i);
                        ArrayList target = classToArrayList.get(obj.getClass());
                        for (int j = 0; j < ar.size(); j++) {
                            SerializableImage sprite = null;
                            Object cast = ar.get(j);
                            if (obj.getClass() == Wall.class) {
                                sprite = new SerializableImage("sprites/wall.png");
                                Wall casted = (Wall) cast;
                                casted.sprite = sprite;
                                target.add(casted);
                            } else if (obj.getClass() == BasicBuilding.class) {
                                sprite = new SerializableImage("sprites/building.png");
                                BasicBuilding casted = (BasicBuilding) cast;
                                casted.sprite = sprite;
                                target.add(casted);
                            } else if (obj.getClass() == Turret.class) {
                                sprite = new SerializableImage("sprites/turret.png");
                                Turret casted = (Turret) cast;
                                casted.sprite = sprite;
                                target.add(casted);
                            } else {
                                System.out.println("Unknown Class");
                                System.exit(1);
                            }



                        }
                    }
                }
            }
            System.out.println("Done loading");
        }


        for (ArrayList<Updateable> it : updateList) { //go through all objects and update them
            for (int i = 0; i < it.size(); i++) {
                Updateable obj = it.get(i);

                if (obj.update(input, game)) {
                    it.remove(obj);
                    i--;
                }
            }
        }
    }

    public void createObjectMap() {
        for (int i = 0; i < saveToMap.size(); i++) {
            saving.add(saveToMap.get(i));
        }
        /*for (int i = 0; i < Game.width - (Game.width / 5); i += 32) {
        for (int j = 0; j < Game.height; j += 32) {
        for (int k = 0; k < saveToMap.size(); k++) {
        for (int l = 0; l < saveToMap.get(k).size(); l++) {
        Collideable obj = (Collideable) saveToMap.get(k).get(l);
        if (obj.getCollision(i + 16, j + 16)) {
        if (i / 32 >= 26) {
        System.out.println(i + "," + j);
        }S
        grid[(i) / 32][(j) / 32] = obj;
        }
        }
        }
        }
        }*/
    }

    public void saveArray(String filename) {
        try {
            FileOutputStream fos = new FileOutputStream(filename);
            ObjectOutputStream out = new ObjectOutputStream(fos);
            out.writeObject(saveToMap);
            out.flush();
            out.close();
        } catch (IOException e) {
            System.out.println(e);
        }
    }

    public void loadArray(String filename) {
        try {
            FileInputStream fis = new FileInputStream(filename);
            ObjectInputStream in = new ObjectInputStream(fis);
            ArrayList read = (ArrayList) in.readObject();
            saveToMap = (ArrayList<ArrayList>) read;

            in.close();

        } catch (Exception e) {
            System.out.println(e);
        }

    }

    private void doNothing() {
        /*
         * EXTREMELY VITAL METHOD TO THE CORRECT FUNCION OF THE GAME! DO NOT CHANGE EVUR!
         */
    }
}
